/**
 * Project hdmap
 * @author shengjialiang
 * @version v1.0
 */


#include "map_common/ObjectMap.h"

/**
 * ObjectMap implementation
 */

namespace Common
{
    
    CObjectMap::CObjectMap()
    {

    }

    CObjectMap::~CObjectMap()
    {

    }

    bool CObjectMap::add(const std::string& in_key, Common::CObject* in_pRefObject)
    {
        bool r = false;
        {
            this->lock();
            if (this->mObjects.find(in_key) == this->mObjects.end())
            {
                this->mObjects[in_key] = in_pRefObject;
                r = true;
            }
            this->unlock();;
        }
        return r;
    }

    int CObjectMap::size()
    {
        int r = 0;
        {
            this->lock();
            r = this->mObjects.size();
            this->unlock();;
        }
        return r;
    }

    std::vector<std::string> CObjectMap::getKeys()
    {
        std::vector<std::string> keys;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator bitr = this->mObjects.begin();
            std::map<std::string, Common::CObject*>::iterator eitr = this->mObjects.end();
            while (bitr != eitr)
            {
                keys.push_back(bitr->first);
                ++bitr;
            }
            this->unlock();;
        }
        return keys;
    }

    bool CObjectMap::exist(const std::string& in_key)
    {
        bool r = false;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator itr = this->mObjects.find(in_key);
            if (itr != this->mObjects.end())
            {
                r = true;
            }
            this->unlock();;
        }
        return r;
    }

    bool CObjectMap::get(std::vector<Common::CObject*>& inout_objects)
    {
        bool r = false;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator bitr = this->mObjects.begin();
            std::map<std::string, Common::CObject*>::iterator eitr = this->mObjects.end();
            while (bitr != eitr)
            {
                inout_objects.push_back(bitr->second);
                r = true;
                ++bitr;
            }
            this->unlock();
        }
        return r;
    }

    Common::CObject* CObjectMap::get(const std::string& in_key)
    {
        Common::CObject* pObject = NULL;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator itr = this->mObjects.find(in_key);
            if (itr != this->mObjects.end())
            {
                pObject = itr->second;
            }
            this->unlock();;
        }
        return pObject;
    }

    Common::CObject* CObjectMap::remove(const std::string& in_key)
    {
        Common::CObject* pObject = NULL;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator itr = this->mObjects.find(in_key);
            if (itr != this->mObjects.end())
            {
                pObject = itr->second;
                this->mObjects.erase(itr);
            }
            this->unlock();;
        }
        return pObject;
    }

    bool CObjectMap::removeAndDestroy(const std::string& in_key)
    {
        bool r = false;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator itr = this->mObjects.find(in_key);
            if (itr != this->mObjects.end())
            {
                CObject* pObject = itr->second;
                this->mObjects.erase(itr);
                delete pObject;
                r = true;
            }
            this->unlock();;
        }
        return r;
    }

    bool CObjectMap::removeAll()
    {
        bool r = false;
        {
            this->lock();
            this->mObjects.clear();
            r = true;
            this->unlock();;
        }
        return r;

    }

    bool CObjectMap::removeAllAndDestroy()
    {
        bool r = false;
        {
            this->lock();
            std::map<std::string, Common::CObject*>::iterator bitr = this->mObjects.begin();
            std::map<std::string, Common::CObject*>::iterator eitr = this->mObjects.end();
            while (bitr != eitr)
            {
                Common::CObject* pObject = bitr->second;
                if (pObject)
                {
                    //delete pObject;
                }
                ++bitr;
            }
            this->mObjects.clear();
            this->unlock();;
        }
        return r;
    }

    void CObjectMap::lock()
    {
        this->mMutex.lock();
    }

    void CObjectMap::unlock()
    {
        this->mMutex.unlock();;
    }
}